package com.settlement.system.parse.formula;

import com.alibaba.excel.util.DateUtils;
import com.settlement.system.model.entity.common.TblOrderAuditReport;
import com.settlement.system.parse.lang.OrderDate;
import lombok.extern.slf4j.Slf4j;

import java.lang.reflect.Method;
import java.math.BigDecimal;
import java.text.ParseException;
import java.util.Date;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

/**
 * 订单稽核占位符处理
 *
 * @author Ximi
 * @since 2020/10/12
 */
@Slf4j
public class OrderPlaceHoldParse implements PlaceHoldParse {

    private TblOrderAuditReport auditReport;
    private Map<String, Object> requestParams;
    private static Map<OrderPlaceHoldEunm, Method> methodMap = new ConcurrentHashMap<>();

    public OrderPlaceHoldParse(TblOrderAuditReport auditReport, Map<String, Object> requestParams) {
        this.auditReport = auditReport;
        this.requestParams = requestParams;
    }

    @Override
    public Object getPlaceHoldValue(String placeHold) {

        if (!isPlaceHold(placeHold)) {
            return null;
        }

        if (placeHold.equals(OrderPlaceHoldEunm.today.getName())) {
            return new OrderDate(new Date());
        }

        if (placeHold.equals(OrderPlaceHoldEunm.searchDate.getName())) {
            try {
                Date outDate = DateUtils.parseDate(requestParams.get("outDate").toString(),"yyyy-MM-dd");
                return new OrderDate(outDate);
            } catch (ParseException e) {
                log.error("解析日期异常", e);
            }
        }

        try {

            OrderPlaceHoldEunm eunm = OrderPlaceHoldEunm.getByName(placeHold);
            Method method = getMethod(eunm);
            if (null != method) {
                Object o = method.invoke(auditReport);

                if (method.getReturnType() == BigDecimal.class) {
                    return getNotEmpty((BigDecimal) o);
                }

                if (method.getReturnType() == Integer.class) {
                    return getNotEmpty((Integer) o);
                }

                if (method.getReturnType() == Date.class) {

                    if(o == null){
                        return new OrderDate(0,0,0);
                    }

                    return new OrderDate((Date) o);
                }
            }
        } catch (Exception e) {
            log.error("反射异常", e);
        }

        return null;
    }

    /**
     * 获取方法
     *
     * @param eunm
     * @return
     */
    private Method getMethod(OrderPlaceHoldEunm eunm) {

        if (methodMap.containsKey(eunm)) {
            return methodMap.get(eunm);
        }

        try {
            String methodName = getMethodName(eunm.getNo());
            Method method = TblOrderAuditReport.class.getMethod(methodName);
            methodMap.put(eunm, method);
            return method;
        } catch (NoSuchMethodException e) {
            log.error("获取方法异常", e);
        }

        return null;
    }

    /**
     * 获取方法名
     *
     * @param str
     * @return
     */
    private String getMethodName(String str) {
        StringBuilder builder = new StringBuilder();
        builder.append("get");
        builder.append(String.valueOf(str.charAt(0)).toUpperCase());
        builder.append(str.substring(1));
        return builder.toString();
    }


    private BigDecimal getNotEmpty(BigDecimal value) {
        return value == null ? BigDecimal.ZERO : value;
    }

    private BigDecimal getNotEmpty(Integer value) {
        return value == null ? BigDecimal.ZERO : BigDecimal.valueOf(value);
    }

    @Override
    public Boolean isPlaceHold(String placeHold) {
        return OrderPlaceHoldEunm.getByName(placeHold) != null;
    }
}
